package eu.irreality.dai.gameplay.actions.movement;

import eu.irreality.dai.gameplay.actions.Action;
import eu.irreality.dai.gameplay.entities.AliveEntity;
import eu.irreality.dai.gameplay.events.GameEvent;
import eu.irreality.dai.gameplay.world.GameWorld;
import eu.irreality.dai.util.Position;
import eu.irreality.dai.world.level.Level;

public abstract class MovementAction extends Action
{

    public MovementAction(GameWorld world, AliveEntity entity)
    {
	super(world, entity);
	baseEnergyCost = 100;
    }

    @Override
    public void execute()
    {
	Level level = world.getActiveLevel();
	Position dest = getDestinationPosition();
	if (entity.getPassabilityCriterion() == null
		|| entity.getPassabilityCriterion().isPassable(level, dest))
	{
	    level.remove(entity, entity.getPosition().getRow(), entity
		    .getPosition().getCol());
	    entity.setPosition(dest);
	    level.add(entity, dest.getRow(), dest.getCol());
	    // if ( entity instanceof PlayerCharacter )
	    // ((PlayerCharacter)entity).updateSeen(level);
	    world.notifyObservers(new GameEvent(level, dest, entity, null,
		    GameEvent.MOVE));

	} else
	{
	    if (entity.equals(world.getPlayerCharacter()))
	    {
		world.notifyObservers(new GameEvent(level, dest, entity, null,
			GameEvent.TRY_TO_MOVE));
	    }
	}
    }

    protected abstract Position getDestinationPosition();
}
